﻿// Copyright (c) 2012 Bryan C. O'Connell
// http://wsubi.codeplex.com/license
// Purpose: Omakase translates to "chef's choice". This class is used to determine the
// proper way to form an execution command line entry for a script based on its type.

using System;
using System.Collections.Generic;

namespace Wsubi
{
    class Omakase
    {
        public Omakase(string FullScriptFilePath, string Params) 
        {
            DetermineExecutableNeeds(FullScriptFilePath);

            BuildCommandStatement(FullScriptFilePath, Params);
        }

        /// <summary>Determines how to execute the specified script based on its type.</summary>
        /// <param name="ScriptFile">The script to be evaluated.</param>
        private void DetermineExecutableNeeds(string ScriptFile)
        {
            string ScriptType = ScriptFile.Remove(0, (ScriptFile.LastIndexOf(".") + 1));
            
            switch (ScriptType)
            { 
                case "bat":
                case "cmd":
                    AssignExecutableValues("cmd.exe", "/C");                    
                    break;

                // BOC: Haven't found a good way to get F# scripts to work yet.
                //case "fsx":
                //    AssignExecutableValues("fsi.exe", "--exec --nologo");
                //    break;

                case "ps1":
                    AssignExecutableValues("powershell.exe", "-command");
                    break;

                case "py":
                    AssignExecutableValues("python.exe", "");
                    break;

                case "rb":
                    AssignExecutableValues("ruby.exe", "");
                    break;

                case "vbs":
                    AssignExecutableValues("cscript.exe", "");
                    break;

                default:
                    throw new ArgumentOutOfRangeException("So sorry, script is not of a supported type.");
            }
        }

        /// <summary>Set values for the Executable and CommandStatement properties.</summary>
        /// <param name="Executable">Name of the .exe that should be used.</param>
        /// <param name="PreCommandValue">Any additional flags or values required by the .exe to run a script.</param>
        private void AssignExecutableValues(string Executable, string PreCommandValue)
        {
            _ExecuteWith = Executable;
            _CommandStatement = PreCommandValue;
        }

        /// <summary>Assembles a valid command statement to run a script file.</summary>
        /// <param name="ScriptFileName">Name of the script file to be executed.</param>
        /// <param name="Params">Any parameters being passed in (appended) to the command statement.</param>
        private void BuildCommandStatement(string ScriptFileName, string Params)
        {
            if (!String.IsNullOrEmpty(_CommandStatement))
            {
                _CommandStatement += " ";
            }

            _CommandStatement += "\"" + ScriptFileName + "\"";

            if (!String.IsNullOrEmpty(Params))
            {
                _CommandStatement += " " + Params;
            }
        }

        #region Properties / Variables

        // Stores the value for the .exe to be used.
        private string _ExecuteWith = "";
        public string ExecuteWith
        { get { return _ExecuteWith; } }

        //  Stores the value for the command to run the script.
        private string _CommandStatement = "";
        public string CommandStatement
        { get { return _CommandStatement; } }

        #endregion
    }
}
